package owl2vowl.knowledgebase.controller;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.sql.SQLException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.UUID;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.FileItemFactory;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.jena.ontology.OntClass;
import org.apache.jena.ontology.OntModel;
import org.apache.jena.ontology.OntModelSpec;
import org.apache.jena.rdf.model.ModelFactory;
import org.semanticweb.owlapi.model.OWLOntologyCreationException;
import org.springframework.beans.factory.annotation.Autowired;
//import org.springframework.mock.web.MockMultipartFile;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.MultipartHttpServletRequest;
import org.springframework.web.multipart.commons.CommonsMultipartFile;

import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;

import owl2vowl.Owl2Vowl;
import owl2vowl.knowledgebase.entity.EntityInfo;
import owl2vowl.knowledgebase.entity.EntityRelation;
import owl2vowl.knowledgebase.entity.KwFileLog;
import owl2vowl.knowledgebase.entity.KwSemantics;
import owl2vowl.knowledgebase.entity.KwSemanticsExample;
import owl2vowl.knowledgebase.entity.OwlFileInfo;
import owl2vowl.knowledgebase.service.EntityInfoService;
import owl2vowl.knowledgebase.service.EntityRelationService;
import owl2vowl.knowledgebase.service.KwFileLogService;
import owl2vowl.knowledgebase.service.KwSemanticsService;
import owl2vowl.knowledgebase.service.OwlFileInfoService;
import owl2vowl.knowledgebase.util.FilePathUtil;
import owl2vowl.knowledgebase.util.R;
import owl2vowl.util.CreateFileUtil;
import owl2vowl.util.JenaAnalysisOwl2Mysql;

@RestController
@RequestMapping("/owlManage")
@SuppressWarnings({ "rawtypes", "unused", "unchecked" })
public class OwlManageController {

	 @Autowired
	 private OwlFileInfoService owlFileInfoService;
	 @Autowired
	 private EntityInfoService entityInfoService;
	 @Autowired
	 private EntityRelationService entityRelationService;
	 @Autowired
	 private KwSemanticsService kwSemanticsService;
	 @Autowired
	 private KwFileLogService kwFileLogService;
	 
	 private SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
	 

	 public static void main(String[] args) throws SQLException

	 {
		 String file = "C://Users//LIUjg//Desktop//工信部一所项目//知识获取//protege//test.owl";
		 String fileName = file.substring(file.lastIndexOf("/")+1);
		 String prefix=fileName.substring(fileName.lastIndexOf("."));
		 int num=prefix.length();//得到后缀名长度
		 String Name= fileName.substring(0, fileName.length()-num);
		 System.out.println(Name);
	 }
	 
	 /**
		 * 上传附件
		 * @return
		 */
		@RequestMapping(value = "/uploadFile", method = RequestMethod.POST,produces="text/html;charset=utf-8")
		@ResponseBody 
		public String uploadFile(HttpServletResponse response,HttpServletRequest request){
			String result="error";
			try {
				MultipartHttpServletRequest multiRequest = (MultipartHttpServletRequest) request;
				Map<String,MultipartFile> files = multiRequest.getFileMap();
				if(files!=null && !files.isEmpty()){
					for (String fileId : files.keySet()) {
						MultipartFile file = files.get(fileId);
						Long size = file.getSize();
						savePic(file.getInputStream(), file.getOriginalFilename(),request,size);
					}
				}
				result = "success";
			} catch (Exception e) {
				// TODO: handle exception
				e.printStackTrace();
			}
			return result;
		}
		
		@RequestMapping(value = "/saveSemantics", method = RequestMethod.POST)
		public R saveSemantics(@RequestParam Map<String, Object> params) {
			try {
				KwSemantics  kwsem = new KwSemantics();
				String semanticsCode = UUID.randomUUID().toString();
				String semanticsName = (String) params.get("semanticsName");
				String relationType = (String) params.get("relationType");
				String relationSemanticsCode = UUID.randomUUID().toString();
				String relationSemanticsName = (String) params.get("relationSemanticsName");
				kwsem.setSemanticsCode(semanticsCode);
				kwsem.setSemanticsName(semanticsName);
				kwsem.setRelationType(relationType);
				kwsem.setRelationSemanticsCode(relationSemanticsCode);
				kwsem.setRelationSemanticsName(relationSemanticsName);
				kwSemanticsService.insert(kwsem);
				return R.ok();
			} catch (Exception e) {
				// TODO: handle exception
				e.printStackTrace();
			}
			return null;
		}
		
		@GetMapping("/getSemanticsList")
		public R getSemanticsList(@RequestParam Map<String, Object> params) {
			try {
				Integer pn = Integer.parseInt(params.get("page") + "");
				PageHelper.startPage(pn, 10);
				List<KwSemantics> KwSemanticss = kwSemanticsService.selectByExample(null);
				PageInfo page = new PageInfo(KwSemanticss, 10);
				return R.ok().put("page", page);
			} catch (Exception e) {
				// TODO: handle exception
				e.printStackTrace();
			}
			return null;
		}
		
		
		/**
		 * 用户后台>产品中心>我的产品(后台分页)查询
		 */
		@RequestMapping(value = "/delSemantics", method = RequestMethod.POST)
		@ResponseBody
		public R delSemantics(HttpServletRequest request,@RequestParam Map<String, Object> mydata){
			try {
				Integer id = Integer.parseInt(mydata.get("id") + "");
				kwSemanticsService.deleteByPrimaryKey(id);
				return R.ok();
			} catch (Exception e) {
				// TODO: handle exception
				e.printStackTrace();
			}
			return null;
			
		}
		
		
		
		/**
		 * 用户后台>产品中心>我的产品(后台分页)查询
		 */
		@RequestMapping(value = "/getSemantics", method = RequestMethod.POST)
		@ResponseBody
		public R getSemantics(HttpServletRequest request,@RequestParam Map<String, Object> mydata){
			try {
				List<KwSemantics> listSe = null;
				List<String> strSE = new ArrayList<String>();
				String searchName = (String) mydata.get("searchName");
				String searchType = (String) mydata.get("searchType");
				strSE.add(searchName);
				if(searchName!=null && !"".equals(searchName) && searchType!=null && !"".equals(searchType)){
					KwSemanticsExample example = new KwSemanticsExample();
					example.createCriteria().andSemanticsNameEqualTo(searchName).andRelationTypeEqualTo(searchType);
					listSe = kwSemanticsService.selectByExample(example);
				}
				if(listSe!=null && listSe.size()>0){
					
					for (int i = 0; i < listSe.size(); i++) {
						strSE.add(listSe.get(i).getRelationSemanticsName());
					}
				}
				Integer pn = Integer.parseInt(mydata.get("page") + "");
				PageHelper.startPage(pn, 8);
				List<KwFileLog> kwList = kwFileLogService.getKwBySemantics(strSE);
				
				PageInfo page = new PageInfo(kwList, 8);
				return R.ok().put("page", page);
			} catch (Exception e) {
				// TODO: handle exception
				e.printStackTrace();
			}
			return null;
			
		}
		/**
		 * 保存文件
		 * @param inputStream
		 * @param fileName
		 */
		private void savePic(InputStream inputStream, String fileName,HttpServletRequest request,Long size) {       
			OutputStream os = null;     
			try {       
				String path = FilePathUtil.FILE_PATH +"owlJson"+File.separator;
				Owl2Vowl arg8 = new Owl2Vowl(inputStream);
				String arg7 = arg8.getJsonAsString();
				String prefix=fileName.substring(fileName.lastIndexOf("."));
				int num=prefix.length();//得到后缀名长度
				String Name= fileName.substring(0, fileName.length()-num);
				CreateFileUtil.createJsonFile(arg7, "", Name);
				//String path = "C:\\temp\\";       
				// 2、保存到临时文件       // 1K的数据缓冲     
				byte[] bs = new byte[1024];       // 读取到的数据长度       
				int len;       // 输出的文件流保存到本地文件        
				File tempFile = new File(path);       
				if (!tempFile.exists()) {         
					tempFile.mkdirs();       
					}       
				os = new FileOutputStream(tempFile.getPath() + File.separator + fileName);       
				// 开始读取      	
				while ((len = inputStream.read(bs)) != -1) {         
				os.write(bs, 0, len);       
				}
				Date now = new Date();
				OwlFileInfo owlInfo = new OwlFileInfo();
				owlInfo.setCreateTime(now);
				owlInfo.setFileName(Name);
				owlInfo.setFilePath(Name);
				owlInfo.setFileSize(Integer.parseInt(String.valueOf(size)));
				//保存实体信息到数据库
				owlFileInfoService.insert(owlInfo);
				
			}catch (Exception e) {       
					e.printStackTrace();     
			} finally {
				// 完毕，关闭所有链接      
				try {         
					os.close();         
					inputStream.close();       
					} catch (IOException e) {         
						e.printStackTrace();       
				}     
						
			}
		}
	 
	 
	 @GetMapping("/getOwlList")
		public R getDocumentList(@RequestParam Map<String, Object> params) {
			Integer pn = Integer.parseInt(params.get("page") + "");
			PageHelper.startPage(pn, 10);
			List<OwlFileInfo> documentsList = owlFileInfoService.selectByExample(null);
			PageInfo page = new PageInfo(documentsList, 10);
			return R.ok().put("page", page);
		}
	 
	 private static MultipartFile getMulFileByPath(String picPath) {  
	        FileItem fileItem = createFileItem(picPath);  
	        MultipartFile mfile = new CommonsMultipartFile(fileItem);  
	        return mfile;  
	    }  
	  
	    private static FileItem createFileItem(String filePath)  
	    {  
	        FileItemFactory factory = new DiskFileItemFactory(16, null);  
	        String textFieldName = "textField";  
	        int num = filePath.lastIndexOf(".");  
	        String extFile = filePath.substring(num);  
	        FileItem item = factory.createItem(textFieldName, "text/plain", true,  
	            "test" + extFile);  
	        File newfile = new File(filePath);  
	        int bytesRead = 0;  
	        byte[] buffer = new byte[8192];  
	        try  
	        {  
	            FileInputStream fis = new FileInputStream(newfile);  
	            OutputStream os = item.getOutputStream();  
	            while ((bytesRead = fis.read(buffer, 0, 8192))  
	                != -1)  
	            {  
	                os.write(buffer, 0, bytesRead);  
	            }  
	            os.close();  
	            fis.close();  
	        }  
	        catch (IOException e)  
	        {  
	            e.printStackTrace();  
	        }  
	        return item;  
	    }  
	 
	 @RequestMapping(value = {"/showOwl"}, method = {RequestMethod.POST})
	 public String uploadOntology(@RequestParam Map<String, Object> params)
				throws IOException, OWLOntologyCreationException {
		 //MultipartFile[] files = null;
		 String aa = (String) params.get("status");
		 ArrayList inputStreams = new ArrayList();

			MultipartFile file = getMulFileByPath("C://Users//LIUjg//Desktop//工信部一所项目//知识获取//protege//test.owl");
			inputStreams.add(file.getInputStream());

		try {
			Owl2Vowl arg8 = new Owl2Vowl((InputStream) inputStreams.get(0));
			String arg7 = arg8.getJsonAsString();
			return arg7;
		} catch (Exception arg6) {
			throw arg6;
		}
					
		 
		}
		
	/**
	 * 
	 * @param filePath owl文件地址
	 * @param modelName   模型名称
	 * @return
	 */
	@RequestMapping("/saveOwl2Mysql")
	public String saveOwl2Mysql(String filePath,String modelName) {
		Date now = new Date();
		String date = sdf.format(now);
		String owlCode = UUID.randomUUID().toString();//owl文件编号
		try {
			if(filePath!=null && modelName!=null && !"".equals(filePath)){
				OwlFileInfo owlInfo = new OwlFileInfo();
				owlInfo.setCreateTime(now);
				owlInfo.setFileName(modelName);
				owlInfo.setFilePath(filePath);
				//保存实体信息到数据库
				owlFileInfoService.insert(owlInfo);
			}
			
			//保存owl文件到mysql数据库
			JenaAnalysisOwl2Mysql.SaveOwl2Mysql(filePath, modelName);
			//保存owl关系到数据库
			saveOwlInfo(filePath, modelName,date,owlCode);
		} catch (Exception e) {
			// TODO: handle exception
			e.printStackTrace();
		}
		return "home/index";
	}
	
	
	/**
	 * 
	 * @param filePath
	 * @param modelName
	 * @param date
	 * @return
	 */
	public int saveOwlInfo(String filePath,String modelName,String date,String owlCode){
		int result = 0;
		try {
			OntModel ontModel = ModelFactory.createOntologyModel(OntModelSpec.OWL_MEM);
	        ontModel.read(new FileInputStream(filePath), "");

	        for (Iterator<?> i = ontModel.listClasses(); i.hasNext();) {
	            OntClass c = (OntClass) i.next(); // 返回类型强制转换
	            if (!c.isAnon()) { // 如果不是匿名类，则打印类的名字
	            	EntityInfo info = new EntityInfo();
	            	info.setCreatedate(date);
	            	info.setEntityName(c.getLocalName());
	            	info.setOwlCode(owlCode);
	            	//info.setEntityPro(entityPro);
	            	//info.setEntityType(entityType);
	            	entityInfoService.insert(info);
	                System.out.print("Class:");
	                System.out.println("localname:"+c.getLocalName());
	                //读取标签名
	                System.out.println("标签名："+c.getLabel(""));

	                //迭代显示当前类的直接父类
	                for (Iterator<?> it = c.listSuperClasses(); it.hasNext();)

	                {
	                    OntClass sp = (OntClass) it.next();
	                    //父类不是匿名类
	                    if (!sp.isAnon()){
	                    	String entity1 = "";
	                    	entity1 = c.getModel().getGraph().getPrefixMapping().shortForm(c.getURI());
	                    	String str = entity1+ "'s superClass is " ; // 获取URI
	                        String strSP = sp.getURI();
	                    	EntityRelation relation = new EntityRelation();
	                    	relation.setEntity1Name(entity1);
	                    	relation.setRelation("superClass");
	                        if(strSP != null){
	                            try{ // 另一种简化处理URI的方法
	                            	relation.setEntity2Name(strSP.substring(strSP.indexOf('#')+1));
	                                str = str + ":" + strSP.substring(strSP.indexOf('#')+1);
	                                System.out.println("Class" +str);

	                            }catch( Exception e ){
	                            	e.printStackTrace();
	                            }
	                        }
	                        entityRelationService.insert(relation);
	                    }

	                } // super class ends

	                System.out.println();
	                ontModel.write(new FileOutputStream(filePath));
	            }
	        }
			result = 1;
		} catch (Exception e) {
			// TODO: handle exception
			e.printStackTrace();
		}
		return result;
	}
	
}
